#!/usr/bin/env bash

. $LKP_SRC/lib/lkp_path.sh

[ -n "$SUDO_USER" ] && HOME=$(eval "echo ~$SUDO_USER")

if [ "${0%isula}" != "$0" ]; then
	DOCKER=isula
elif [ "${0%podman}" != "$0" ]; then
	DOCKER=podman
else
	DOCKER=docker
fi

usage()
{
	cat <<EOF
Usage:
	lkp docker [options] build DOCKER_IMAGE
	lkp docker [options] run DOCKER_IMAGE JOB_YAML [key=val ...]

Example:
	# This creates 'lkp-debian:11' docker image locally with generated
	# ~/.cache/lkp/container/Dockerfile.debian:11
	#	FROM debian:11
	#	COPY lkp-src /c/lkp-tests
	#	RUN /c/lkp-tests/sbin/install-dependencies.sh
	lkp docker -m build debian:11
	# You may now run this to enable/debug tests:
	# 	docker run -it -v $LKP_SRC:/c/lkp-tests debian:11 bash

	# This runs /bin/bash in the above created 'lkp-debian:11'.
	lkp docker run debian:11

	# This runs lkp-run.yaml with parameter 'job=stream.yaml'
	# which install-and-runs stream.yaml in 'lkp-debian:11'.
	lkp docker -m run debian:11 lkp-run.yaml job=stream.yaml

Options:
	-m	bind mount $HOME/.cache/lkp        into /root/.cache/lkp

Note:
This script runs JOB_YAML in DOCKER_IMAGE, mounting LKP_SRC to /c/lkp-tests
Results are stored under /root/.cache/lkp/results in container.
EOF
	exit 1
}

while getopts "m" opt
do
	case $opt in
		m ) opt_mount_lkp="-v $HOME/.cache/lkp:/root/.cache/lkp" ;;
		? ) usage ;;
	esac
done

shift $((OPTIND-1))

opt_action=$1
opt_image=$2
opt_job=$3
shift 3
opt_job_kv="$@"

[ "$opt_action" != 'build' ] && [ "$opt_action" != 'run' ] && usage
[ -n "$opt_image" ] || usage
IMAGE_TAG=lkp-$opt_image
DOCKERFILE=${opt_image//\//_}

[ -n "$opt_mount_lkp" ] || opt_mount_lkp="-v $HOME/.cache/lkp/result:/root/.cache/lkp/result"

prepare_workdir()
{
	mkdir -p lkp-src/{lib,bin,sbin,lkp-exec,programs,hosts}
	cp -au $LKP_SRC/sbin/install-dependencies.sh 	lkp-src/sbin/
	cp -au $LKP_SRC/sbin/pkgmap			lkp-src/sbin
	cp -au $LKP_SRC/bin/lkp				lkp-src/bin/
	cp -au $LKP_SRC/lkp-exec/install		lkp-src/lkp-exec/
	cp -au $LKP_SRC/lib/detect-system.sh 		lkp-src/lib
	cp -au $LKP_SRC/lib/env.sh			lkp-src/lib
	cp -au $LKP_SRC/lib/tbox.sh			lkp-src/lib
	cp -au $LKP_SRC/lib/debug.sh			lkp-src/lib
	cp -au $LKP_SRC/lib/result.sh			lkp-src/lib
	cp -au $LKP_SRC/lib/install.sh			lkp-src/lib
	cp -au $LKP_SRC/lib/lkp_cmd.sh			lkp-src/lib
	cp -au $LKP_SRC/lib/lkp_path.sh			lkp-src/lib
	cp -au $LKP_SRC/lib/constant.sh			lkp-src/lib
	cp -au $LKP_SRC/lib/run-env.sh			lkp-src/lib
	cp -au $LKP_SRC/lib/pkgmap.rb			lkp-src/lib
	cp -au $LKP_SRC/lib/distro_info.rb		lkp-src/lib
	cp -au $LKP_SRC/Gemfile*			lkp-src/
	cp -au $LKP_SRC/distro				lkp-src/
	cp -au $LKP_SRC/programs/lkp-tests		lkp-src/programs
	cp -au $LKP_SRC/programs/makepkg		lkp-src/programs
}

create_dockerfile()
{
	cat > $DOCKERFILE <<-EOF
	FROM $opt_image
	COPY lkp-src /c/lkp-tests
	RUN /c/lkp-tests/sbin/install-dependencies.sh
	EOF
}

should_skip_rebuild()
{
	[ "$opt_action" = 'build' ] && return 1

	$DOCKER image inspect $IMAGE_TAG >/dev/null 2>&1
}

build_container()
{
	should_skip_rebuild && return
	local cmd="$DOCKER build --no-cache=true -t $IMAGE_TAG -f $DOCKERFILE ."
	echo $cmd
	$cmd
}

run_container()
{
	[ "$opt_action" = 'run' ] || return 0

	if [ -n "$opt_job" ]; then
		find_job "$opt_job" || exit
		local CMD=("/c/lkp-tests/bin/install-run-job" "${job_file#$LKP_SRC/}" "${opt_job_kv[@]}")
		local IT=
	else
		local IT=-it
		local CMD=bash
	fi

	local cmd=(
		$DOCKER run
		$IT
		-v $LKP_SRC:/c/lkp-tests
		$opt_mount_lkp
		$IMAGE_TAG
	)
	echo "${cmd[@]}" "${CMD[@]}"
	"${cmd[@]}" "${CMD[@]}"
}

WORK_DIR=$HOME/.cache/lkp/container
mkdir -p $WORK_DIR
cd $WORK_DIR

prepare_workdir
create_dockerfile
build_container
run_container
